package cc.rengu.igas.share.core.service.asyncall;

import cc.rengu.igas.momp.facade.response.ComboPaymentRefundResponse;
import cc.rengu.igas.momp.facade.result.Result;
import cc.rengu.oltp.service.base.DubboAsynBaseService;
import cc.rengu.oltp.service.common.constant.TreeNodeConstant;
import cc.rengu.oltp.service.common.dao.PayOrderInfoMapper;
import cc.rengu.oltp.service.common.dao.impl.PayOrderInfoMapperImpl;
import cc.rengu.oltp.service.common.entity.PayOrderInfo;
import cc.rengu.oltp.service.common.enums.BizStatusEnum;
import cc.rengu.oltp.service.common.enums.ChannelEnum;
import cc.rengu.oltp.service.common.enums.OltpRpcdEnum;
import cc.rengu.oltp.service.common.enums.TransStatusEnum;
import cc.rengu.oltp.service.model.BizException;
import cc.rengu.oltp.service.realize.OrderService;
import cc.rengu.oltp.service.realize.impl.OrderServiceImpl;
import cc.rengu.oltp.utility.annotation.BIZ_PROCESS;
import cc.rengu.oltp.utility.util.DateUtil;
import cc.rengu.oltp.utility.util.XmlTreeUtil;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;

import java.util.List;
import java.util.stream.Collectors;

/**
 * 营销优惠退款异步处理
 */
public class AsynComboPaymentReturnService extends DubboAsynBaseService {

    @BIZ_PROCESS
    public void comboPaymentReturn() throws Exception {

        XmlTreeUtil xmlTreeUtil = new XmlTreeUtil();
        String sysNo;
        String instId;

        /*判断记账结果，更新支付订单状态*/
        if (!xmlTreeUtil.isExist(TreeNodeConstant.DUBBO_RESPONSE)) {
            rglog.error("dubbo调用营销优惠退款失败,抛出调用业务系统失败的异常，继续存储转发");
            throw new BizException(OltpRpcdEnum.CALL_BIZ_SERVICE_ERROR.getRespCode(), OltpRpcdEnum.CALL_BIZ_SERVICE_ERROR.getRespDesc());
        }

        rglog.debug("dubbo调用通讯成功，获取到调用结果...");
        Result<JSONObject> responseResult = (Result<JSONObject>) xmlTreeUtil.getXmlTreeObjectValue(TreeNodeConstant.DUBBO_RESPONSE, Result.class);
        if (!responseResult.isSuccess()) {
            rglog.error("dubbo调用营销优惠退款失败,抛出调用业务系统失败的异常，继续存储转发");
            throw new BizException(OltpRpcdEnum.CALL_BIZ_SERVICE_ERROR.getRespCode(), OltpRpcdEnum.CALL_BIZ_SERVICE_ERROR.getRespDesc());
        }

        ComboPaymentRefundResponse response = JSON.toJavaObject(responseResult.getResult(), ComboPaymentRefundResponse.class);
        /*避免支付成功发起记账跟查询交易发起记账系统流水号不一致的问题,取调用虚拟账户记账的traceNo*/
        if (response.getHeader() != null && response.getHeader().getTraceNo() != null) {
            sysNo = response.getHeader().getTraceNo().substring(0, 32);
            instId = xmlTreeUtil.getXmlTreeStringValue(TreeNodeConstant.INST_ID);
        } else {
            rglog.error("dubbo调用营销优惠退款失败,响应报文头为空。抛出调用业务系统失败的异常，继续存储转发");
            throw new BizException(OltpRpcdEnum.CALL_BIZ_SERVICE_ERROR.getRespCode(), OltpRpcdEnum.CALL_BIZ_SERVICE_ERROR.getRespDesc());
        }

        /*获取支付订单列表*/
        PayOrderInfoMapper payOrderInfoMapper = new PayOrderInfoMapperImpl();
        List<PayOrderInfo> payOrderInfoList = payOrderInfoMapper.selectPayOrderInfoBySysSeqNum(instId, sysNo);
        if (payOrderInfoList == null || payOrderInfoList.size() == 0) {
            rglog.error("根据机构号<{}>、系统流水号<{}>获取支付订单列表失败", instId, sysNo);
            return;
        }
        List<PayOrderInfo> payOrderInfoListAcct = payOrderInfoList.stream().filter(item -> item.getMsgDstId().equals(ChannelEnum.MOMP.getChannelType())
                && "P04MO002".equals(item.getDstTxnNum())).collect(Collectors.toList());
        if (payOrderInfoListAcct.size() != 1) {
            rglog.error("查询营销支付订单流水记录异常");
            return;
        }
        PayOrderInfo payOrderInfo = payOrderInfoListAcct.get(0);


        OrderService orderService = new OrderServiceImpl();
        if (!OltpRpcdEnum.TRANS_SUCCESS.getRespCode().equals(response.getRespCode())) {
            rglog.warn("业务处理失败respCode<{}>,respDesc<{}>", response.getRespCode(), response.getRespDesc());
            if (BizStatusEnum.PROCESSING.getStatus().equals(payOrderInfo.getBizStatus())) {
                /*更新支付订单表失败*/
                payOrderInfo.setTransStatus(TransStatusEnum.SYSTEM_REJECT.getStatus());
                payOrderInfo.setBizStatus(BizStatusEnum.FINISH.getStatus());
                payOrderInfo.setUpdateTime(DateUtil.getCurrentDateTime("yyyy-MM-dd HH:mm:ss.SSS"));
                if (!orderService.updateOrderInfo(null, null, payOrderInfo)) {
                    rglog.error("更新订单表状态失败");
                }
                return;
            } else {
                rglog.error("订单[{}]业务状态[{}]非业务处理中.不更新", payOrderInfo.getSysSeqNum(), payOrderInfo.getBizStatus());
                return;
            }
        }

        /*更新支付订单表成功*/
        rglog.info("营销退款服务调用成功，更新退款营销支付订单表");
        payOrderInfo.setTransStatus(TransStatusEnum.TRANS_SUCC.getStatus());
        payOrderInfo.setBizStatus(BizStatusEnum.FINISH.getStatus());
        payOrderInfo.setUpdateTime(DateUtil.getCurrentDateTime("yyyy-MM-dd HH:mm:ss.SSS"));
        if (!orderService.updateOrderInfo(null, null, payOrderInfo)) {
            rglog.error("更新订单表状态失败");
        }

        /*获取原支付订单列表*/
        rglog.info("获取原支付交易的营销支付订单信息，更新其业务状态");
        List<PayOrderInfo> oriPayOrderInfoList = payOrderInfoMapper.selectPayOrderInfoBySysSeqNum(instId, payOrderInfo.getOrigSysSeqNum());
        if (payOrderInfoList.size() == 0) {
            rglog.error("根据机构号<{}>、系统流水号<{}>获取原支付订单列表失败", instId, payOrderInfo.getOrigSysSeqNum());
            return;
        }
        List<PayOrderInfo> oriPayOrderInfoListMomp = oriPayOrderInfoList.stream().filter(item -> item.getMsgDstId().equals(ChannelEnum.MOMP.getChannelType())
                && "P01MO003".equals(item.getDstTxnNum())).collect(Collectors.toList());
        if (payOrderInfoListAcct.size() != 1) {
            rglog.error("查询营销支付订单流水记录异常");
            return;
        }
        PayOrderInfo oriPayOrderInfoMomp = oriPayOrderInfoListMomp.get(0);
        oriPayOrderInfoMomp.setBizStatus(BizStatusEnum.REFUND.getStatus());
        if (!orderService.updateOrderInfo(null, null, oriPayOrderInfoMomp)) {
            rglog.error("更新订单表状态失败");
        }
    }
}
